package uiLayer;

import java.awt.EventQueue;

import javax.swing.*;

import modelLayer.ClassContainer;
import modelLayer.UMLClass;

import java.awt.*;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import java.io.*;
import java.util.ArrayList;

public class Main extends JPanel implements ActionListener{

	private JFrame frame;
	final JFileChooser fc = new JFileChooser();
	private JButton btnOpen, btnGo;
	private JTextArea textArea;
	private File umlFile;
	private String filePath;
	private String umlPath;
	/**
	 * Launch the application.
	 */
	public static void main(String[] args) {
		EventQueue.invokeLater(new Runnable() {
			public void run() {
				try {
					Main window = new Main();
					window.frame.setVisible(true);
				} catch (Exception e) {
					e.printStackTrace();
				}
			}
		});
	}

	/**
	 * Create the application.
	 */
	public Main() {
		initialize();
	}

	/**
	 * Initialize the contents of the frame.
	 */
	private void initialize() {
		frame = new JFrame();
		frame.setBounds(100, 100, 453, 623);
		frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		frame.getContentPane().setLayout(null);
		
		btnOpen = new JButton("Open");
		btnOpen.addActionListener(this);
		
		btnOpen.setBounds(10, 11, 89, 23);
		frame.getContentPane().add(btnOpen);
		
		btnGo = new JButton("Go");
		btnGo.addActionListener(this);
		btnGo.setBounds(109, 11, 89, 23);
		frame.getContentPane().add(btnGo);
		
		JScrollPane scrollPane = new JScrollPane();
		scrollPane.setBounds(10, 40, 417, 533);
		frame.getContentPane().add(scrollPane);
		
		textArea = new JTextArea();
		scrollPane.setViewportView(textArea);
	}

	@Override
	public void actionPerformed(ActionEvent e) {
		if (e.getSource() == btnOpen) {
            int returnVal = fc.showOpenDialog(Main.this);

            if (returnVal == JFileChooser.APPROVE_OPTION) {
                umlFile = fc.getSelectedFile();
                filePath = umlFile.getAbsolutePath().substring(0, umlFile.getAbsolutePath().lastIndexOf(File.separator));
                //textArea.append(filePath);
            } else {
                
            }
        }
		
		if(e.getSource() == btnGo){
			if(umlFile != null){
				ClassContainer cCont = ClassContainer.getInstance();
				String nL = System.getProperty("line.separator");
				boolean isClass = false;
				try {
					BufferedReader bf;
					bf = new BufferedReader(new FileReader(umlFile));
					String line;
					UMLClass umlClass = null;
					while((line = bf.readLine()) != null){
						if(line.contains("<panel_attributes>") && !line.contains("lt=")){
							isClass = true;
							String className = line.replace("<panel_attributes>", "").trim();
							umlClass = new UMLClass(className);
						}
						if(line.contains("</panel_attributes>") && !line.contains("lt=")){
							isClass = false;
							cCont.addClass(umlClass);
						}
						if(isClass){
							if(line.contains("Package::")){
								umlClass.setPackage(line.replace("Package::", ""));
							} else if(line.contains("(")){
								umlClass.addMethod(line);
							} else if(line.contains(":")){
								umlClass.addVariable(line);
							}
						}
					}
				} catch (FileNotFoundException e1) {
					// TODO Auto-generated catch block
					e1.printStackTrace();
				} catch (IOException e1) {
					// TODO Auto-generated catch block
					e1.printStackTrace();
				}
				ArrayList<UMLClass> classes = cCont.getAll();
				if(classes != null){
					umlPath = filePath + "/UMLToClass";
					boolean makeDir = (new File(umlPath)).mkdir();

					for(UMLClass c : classes){
						// textArea.append(c.getName() + nL + c.getPackageName() + nL);
						String classPath = umlPath + "/" + c.getPackageName();
						boolean makeDirPack = (new File(classPath)).mkdir();
						if(makeDirPack){
							textArea.append("Creating directory for: " + c.getPackageName() + " - Done" + nL);
						}
						String classFile = classPath + "/" + c.getName() + ".java";
						new File(classFile);
						try {
							Writer writer = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(classFile), "UTF-8"));
							textArea.append("Creating Class file: " + c.getName() + ".java - Done" + nL);
							
							writer.append("package " + c.getPackageName() + ";" + nL + nL);
							writer.append("public class " + c.getName() + " {" + nL);
							
							ArrayList<String> rVars = new ArrayList<String>();
							
							ArrayList<String> vars = c.getVars();
							if(vars != null){
								for(String var : vars){
									String rVar = writeSimpleVar(var);
									writer.append("\t" + rVar + nL);
									rVars.add(rVar);
								}
								textArea.append("Generating instance variables - Done" + nL);
							}
							
							writer.append(nL + "\tpublic " + c.getName() + "() {" + nL + nL + "\t}" + nL + nL);
							
							ArrayList<String> methods = c.getMethods();
							if(methods != null){
								for(String method : methods){
									writer.append(writeMethod(method) + nL + nL);
								}
								textArea.append("Generating methods - Done" + nL);
							}
							
							writer.append(nL + nL);
							
							if(rVars != null){
								for(String rvar : rVars){
									writer.append(writeSetAndGet(rvar));
								}
								textArea.append("Generating setters and getters - Done" + nL);
							}
							textArea.append(nL);
							writer.append("}");
							
							writer.close();
						} catch (UnsupportedEncodingException
								| FileNotFoundException e1) {
							// TODO Auto-generated catch block
							e1.printStackTrace();
						} catch (IOException e1) {
							// TODO Auto-generated catch block
							e1.printStackTrace();
						}
					}
				}
			}
		}
		
	}
	private String writeSetAndGet(String line){
		String words[] = line.split(" ");
		String setGet = "";
		String nL = System.getProperty("line.separator");
		words[2] = words[2].substring(0, words[2].length() - 1);
		
		String upper = words[2];
		
		char firstupper = Character.toUpperCase(upper.charAt(0));
		
		upper = firstupper + upper.substring(1);
		
		String comment1 = "    /**" + nL;
		String comment2 = "    * get" + upper + " - Returns the " + upper + "\n	* @return " + words[2] + nL;
		String comment3 = "    */" + nL;
		String word1 = "	public " + words[1] + " get" + upper + "(){" + nL;
		String word2 = "		return " + words[2] + ";" + nL;
		String word3 = "	}" + nL;
		
		String comment4 = "    * set" + upper + " - sets the " + upper + nL + "	* @param " + words[1] + " " + words[2] + nL;
		
		String word4 = "	public void set" + upper + "(" + words[1] + " " + words[2] + "){" + nL;
		String word5 = "		this." + words[2] + " = " + words[2] + ";" + nL;
		String word6 = "	}" + nL;
		
		setGet = comment1 + comment2 + comment3 + word1 + word2 + word3 + nL + comment1 + comment4 + comment3 + word4 + word5 + word6 + nL;
		
		
		return setGet;
	}
	
	private String writeSimpleVar(String test) {
		String nL = System.getProperty("line.separator");
		String words[] = test.split(" ");
		String meth = "";
		
		if(words[0].charAt(0) == '_'){
			if(words[0].charAt(1) == '+'){
				meth += "public static ";
			}else if(words[0].charAt(1) == '-'){
				meth += "private static ";
			}else if(words[0].charAt(1) == '#'){
				meth += "protected static ";
			}
			meth += words[2] + " ";
			meth += words[1].replace(":", ";");
		} else {
			if(words[0].charAt(0) == '+'){
				meth += "public ";
			}else if(words[0].charAt(0) == '-'){
				meth += "private ";
			}else if(words[0].charAt(0) == '#'){
				meth += "protected ";
			}
			meth += words[2] + " ";
			meth += words[1].replace(":", ";");
		}
		
		return meth;
	}
	
	private String writeMethod(String test){
		String nL = System.getProperty("line.separator");
		String param = "";
		
		String meth = "";
		if(test.indexOf("(") != test.indexOf(")")-1){
			String parameters = test.substring(test.indexOf("(")+1, test.indexOf(")"));
			String rest = test.substring(0, test.indexOf("(")+1) + test.substring(test.indexOf(")"), test.length());
			
			String words[] = rest.split(" ");
			words[1] = words[1].substring(0, words[1].indexOf("(")+1) + parameters + words[1].substring(words[1].indexOf(")"), words[1].length());
			if(words[0].charAt(0) == '_'){
				if(words[0].charAt(1) == '+'){
					meth += "\tpublic static ";
				}else if(words[0].charAt(1) == '-'){
					meth += "\tprivate static ";
				}
				String ret = "";
				if(words.length > 2 & words[2].equals(":")){
					String retType = words[3];
					if(retType.charAt(retType.length()-1) == '_'){
						retType = retType.substring(0, retType.length()-2);
					}
					meth += retType + " ";
					ret = "\t\t//TODO - Auto Generated" + nL + "\t\treturn null;";
				} else {
					meth += "void ";
					ret = "\t\t//TODO - Auto Generated";
				}
				
				meth += words[1] + "{" + nL + ret + nL + "	}";
			}else if(words.length > 2 & (words[0].charAt(0) == '+' || words[0].charAt(0) == '-')){
				if(words[0].charAt(0) == '+'){
					meth += "\tpublic ";
				}else if(words[0].charAt(0) == '-'){
					meth += "\tprivate ";
				}
				
				String retType = words[3];
				if(retType.charAt(retType.length()-1) == '_'){
					retType = retType.substring(0, retType.length()-2);
				}
				meth += retType + " " + words[1] + "{" + nL + "\t\t//TODO - Auto Generated" + nL + "\t}";
				
			}else if(words[0].charAt(0) == '+' || words[0].charAt(0) == '-'){
				if(words[0].charAt(0) == '+'){
					meth += "\tpublic ";
				}else if(words[0].charAt(0) == '-'){
					meth += "\tprivate ";
				}
				String methName = words[1];
				if(methName.charAt(methName.length()-1) == ';'){
					methName = methName.substring(0, methName.length()-1);
				}

				meth += "void " + methName + "{" + nL + "\t\t//TODO - Auto Generated" + nL + "\t}";
			}
		} else {
			String words[] = test.split(" ");
			if(words[0].charAt(0) == '_'){
				if(words[0].charAt(1) == '+'){
					meth += "\tpublic static ";
				}else if(words[0].charAt(1) == '-'){
					meth += "\tprivate static ";
				}
				String ret = "";
				if(words.length > 2 & words[2].equals(":")){
					String retType = words[3];
					if(retType.charAt(retType.length()-1) == '_'){
						retType = retType.substring(0, retType.length()-2);
					}
					meth += retType + " ";
					ret = "\t\t//TODO - Auto Generated" + nL + "\t\treturn null;";
				} else {
					meth += "void ";
					ret = "\t\t//TODO - Auto Generated";
				}
				
				meth += words[1] + "{" + nL + ret + nL + "\t}";
			}else if(words.length > 2 && (words[0].charAt(0) == '+' || words[0].charAt(0) == '-')){
				if(words[0].charAt(0) == '+'){
					meth += "\tpublic ";
				}else if(words[0].charAt(0) == '-'){
					meth += "\tprivate ";
				}
				String retType = words[3];
				if(retType.charAt(retType.length()-1) == '_'){
					retType = retType.substring(0, retType.length()-2);
				}
				String ret = "\t\t//TODO - Auto Generated" + nL + "\t\treturn null;";
				meth += retType + " " + words[1] + "{" + nL + ret + nL + "\t}";
				
			}else if(words[0].charAt(0) == '+' || words[0].charAt(0) == '-'){
				if(words[0].charAt(0) == '+'){
					meth += "\tpublic ";
				}else if(words[0].charAt(0) == '-'){
					meth += "\tprivate ";
				}
				String methName = words[1];
				if(methName.charAt(methName.length()-1) == ';'){
					methName = methName.substring(0, methName.length()-1);
				}

				meth += "void " + methName + "{" + nL + "\t\t//TODO - Auto Generated" + nL + "\t}";
			}

		}
		return meth;
	}
}
